Skip to content

KAFKA-7140: Remove deprecated poll usages - #5319

Merged
hachikuji merged 11 commits into
apache:trunkfrom
viktorsomogyi:example_deprecated_poll
Aug 11, 2018
Merged

KAFKA-7140: Remove deprecated poll usages#5319
hachikuji merged 11 commits into
apache:trunkfrom
viktorsomogyi:example_deprecated_poll

Conversation

@viktorsomogyi

Copy link
Copy Markdown
Contributor

Committer Checklist (excluded from commit message)

  • Verify design and implementation
  • Verify test coverage and CI build status
  • Verify documentation (including upgrade notes)

@ijuma

ijuma commented Jul 2, 2018

Copy link
Copy Markdown
Member

Thanks for the PR. Maybe we can update all non-test usages of the deprecated method at once?

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

@ijuma thanks for the suggestion, I've updated the PR.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@mjsax I think you authored the change where this line was introduced. Do you know what's the reasoning for poll(1)? Did it just used the fact that it updated the metadata or were there any other reasons? I'm not sure that my change is correct here and I don't have the context.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, we do this call to update the metadata. The change seems reasonable to me.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are you sure about this? poll(1) would previously have guaranteed that the consumer joins the group. That is no longer the case with the new poll, so the call to assignment below is likely to return an empty set.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because StreamsResetter must be the only member in the group (we check on startup that the group is empty), we can check if the assignment contains all offsets? Or we could switch to manual assignment?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I think manual assignment is a better option here. For one thing, it guarantees that there won't be another member in the group when you receive the assignment. It also gets around the awkward use of poll() since you do not actually want to fetch data. The basic approach would be to use the partitionsFor API to find the partitions for the subscribed topics and then assign them directly with assign.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, I'll try to refactor my code this way.

@viktorsomogyi viktorsomogyi changed the title MINOR: use poll(Duration) in consumer example KAFKA-7140: Remove deprecated poll usages Jul 9, 2018
@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

Also created a jira for this as it I think it now exceeds the "minor" category :)

@hachikuji

Copy link
Copy Markdown
Contributor

@viktorsomogyi Thanks for the patch. Note that there is a semantic difference between the old and new poll APIs. The old API blocked if a rebalance was in progress, but the new one does not. You may need to review each usage individually to be sure that the new semantic is still appropriate.

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

retest this please

@viktorsomogyi

viktorsomogyi commented Aug 8, 2018

Copy link
Copy Markdown
Contributor Author

@hachikuji thanks for the note. Yes, I've been trying to keep in mind that poll(0) differs in this case. In some cases we could just use to the position call or poll(0) just because we make sure to have an initial value to an iterator, etc.
The only case I found so far where I'm not sure is in StreamsResetter.

@hachikuji hachikuji left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Apologies for the delay. Left a couple comments.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe we can just initialize this to an empty iterator? The call seems intended to join the group, but that will no longer happen when the call returns.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Were you thinking about something like this?
var recordIter = Collections.emptyList[ConsumerRecord[Array[Byte], Array[Byte]]]().iterator()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As far as I can tell, the assignment will be empty here. I don't think the old code worked either as intended because it did the seekToEnd prior to the call to poll(). For an end-to-end latency test, I actually wonder if we should just use manual assignment and take the group management out of the picture?

@viktorsomogyi viktorsomogyi Aug 9, 2018

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will change to manual assignment, something like this (which seems to work).

val topicPartitions = consumer.listTopics().get(topic).asScala
      .map(pi => new TopicPartition(pi.topic(), pi.partition()))
      .to[List].asJava
    consumer.assign(topicPartitions)
    consumer.seekToEnd(topicPartitions)
    consumer.assignment().asScala.foreach(consumer.position)

@viktorsomogyi
viktorsomogyi force-pushed the example_deprecated_poll branch 2 times, most recently from c53957e to 6ae1afa Compare August 9, 2018 14:58

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So here it seems the old code assumed that there is a topic. Now I added a check that there must be a topic beforehand. the producer would anyway create it according to the default settings but I think that most of the latency tests executed by users won't depend on the default settings and they rather want to create topics manually according to their likings.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess another approach might be to produce a dummy record to the topic first before assigning the partitions to the consumer and starting the test. That would let us retain the existing behavior.

@viktorsomogyi
viktorsomogyi force-pushed the example_deprecated_poll branch from bcf8279 to 6ad6f5e Compare August 9, 2018 16:44
try (final KafkaConsumer<byte[], byte[]> client = new KafkaConsumer<>(config, new ByteArrayDeserializer(), new ByteArrayDeserializer())) {
client.subscribe(topicsToSubscribe);
client.poll(1);
Map<String, List<PartitionInfo>> pi = client.listTopics();

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not final yet, will refactor it a bit as suggested in earlier comments.

try (final KafkaConsumer<byte[], byte[]> client = new KafkaConsumer<>(config, new ByteArrayDeserializer(), new ByteArrayDeserializer())) {
client.subscribe(topicsToSubscribe);
client.poll(1);
Collection<TopicPartition> partitions = topicsToSubscribe.stream().map(client::partitionsFor)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@hachikuji were you thinking of something like this?

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Java 8 makes this much nicer than I was expecting. 😄

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

General update:

  • some fixes around suggestions from review
  • fixed test failures (some polls there needed to be replaced)
  • rebased on latest trunk

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

retest this please

@mjsax

mjsax commented Aug 9, 2018

Copy link
Copy Markdown
Member

@viktorsomogyi There is a checkstyle error

/home/jenkins/jenkins-slave/workspace/kafka-pr-jdk10-scala2.12/core/src/main/scala/kafka/tools/StreamsResetter.java:36:8: Unused import - org.apache.kafka.common.PartitionInfo. [UnusedImports

@hachikuji hachikuji left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the updates. Just one comment for discussion.

try (final KafkaConsumer<byte[], byte[]> client = new KafkaConsumer<>(config, new ByteArrayDeserializer(), new ByteArrayDeserializer())) {
client.subscribe(topicsToSubscribe);
client.poll(1);
Collection<TopicPartition> partitions = topicsToSubscribe.stream().map(client::partitionsFor)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Java 8 makes this much nicer than I was expecting. 😄

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess another approach might be to produce a dummy record to the topic first before assigning the partitions to the consumer and starting the test. That would let us retain the existing behavior.

@hachikuji

Copy link
Copy Markdown
Contributor

@viktorsomogyi Thanks for the update. LGTM overall. I think to fix the failing tests, we just need to use the right poll() in WorkerSinkTaskThreadedTest.

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

Ah, indeed. If you haven't started fixing it yet, I pushed a commit with that. Let's see if we'll have any after this. :)

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

It seems there was a flaky afterall. I'll rerun them.

@viktorsomogyi

Copy link
Copy Markdown
Contributor Author

retest this please

@hachikuji
hachikuji merged commit 8a78d76 into apache:trunk Aug 11, 2018
@tedyu

tedyu commented Aug 11, 2018

Copy link
Copy Markdown
Contributor

Can this be dropped from Consumer (in trunk) ?

    ConsumerRecords<K, V> poll(long timeout);

@mjsax

mjsax commented Aug 12, 2018

Copy link
Copy Markdown
Member

@tedyu We cannot just remove a method from public API, as this would be a breaking change. Note, that the method is already deprecated though.

@viktorsomogyi
viktorsomogyi deleted the example_deprecated_poll branch August 23, 2018 13:10
ewencp pushed a commit that referenced this pull request Nov 30, 2018
EndToEndLatency tool produces a dummy record in case the topic does not exist. This behavior was introduced in this PR #5319  as part of updating the tool to use latest consumer API. However, if we run the tool with producer acks == 1, the high watermark may not be updated before we reset consumer offsets to latest. In rare cases when this happens, the tool will throw an exception in the for loop where the consumer will unexpectedly consume the dummy record. As a result, we occasionally see Benchmark.test_end_to_end_latency system test failures.

This PR checks if topic exists, and creates the topic using AdminClient if it does not exist.

Author: Anna Povzner <anna@confluent.io>

Reviewers: Ismael Juma <ismael@juma.me.uk>, Ewen Cheslack-Postava <ewen@confluent.io>

Closes #5950 from apovzner/fix-EndToEndLatency

(cherry picked from commit 3acebe6)
Signed-off-by: Ewen Cheslack-Postava <me@ewencp.org>
ewencp pushed a commit that referenced this pull request Nov 30, 2018
EndToEndLatency tool produces a dummy record in case the topic does not exist. This behavior was introduced in this PR #5319  as part of updating the tool to use latest consumer API. However, if we run the tool with producer acks == 1, the high watermark may not be updated before we reset consumer offsets to latest. In rare cases when this happens, the tool will throw an exception in the for loop where the consumer will unexpectedly consume the dummy record. As a result, we occasionally see Benchmark.test_end_to_end_latency system test failures.

This PR checks if topic exists, and creates the topic using AdminClient if it does not exist.

Author: Anna Povzner <anna@confluent.io>

Reviewers: Ismael Juma <ismael@juma.me.uk>, Ewen Cheslack-Postava <ewen@confluent.io>

Closes #5950 from apovzner/fix-EndToEndLatency
ijuma pushed a commit to confluentinc/kafka that referenced this pull request Dec 3, 2018
EndToEndLatency tool produces a dummy record in case the topic does not exist. This behavior was introduced in this PR apache#5319  as part of updating the tool to use latest consumer API. However, if we run the tool with producer acks == 1, the high watermark may not be updated before we reset consumer offsets to latest. In rare cases when this happens, the tool will throw an exception in the for loop where the consumer will unexpectedly consume the dummy record. As a result, we occasionally see Benchmark.test_end_to_end_latency system test failures.

This PR checks if topic exists, and creates the topic using AdminClient if it does not exist.

Author: Anna Povzner <anna@confluent.io>

Reviewers: Ismael Juma <ismael@juma.me.uk>, Ewen Cheslack-Postava <ewen@confluent.io>

Closes apache#5950 from apovzner/fix-EndToEndLatency

(cherry picked from commit 3acebe6)
Signed-off-by: Ewen Cheslack-Postava <me@ewencp.org>
pengxiaolong pushed a commit to pengxiaolong/kafka that referenced this pull request Jun 14, 2019
Reviewers: Matthias J. Sax <mjsax@apache.org>, Jason Gustafson <jason@confluent.io>
pengxiaolong pushed a commit to pengxiaolong/kafka that referenced this pull request Jun 14, 2019
EndToEndLatency tool produces a dummy record in case the topic does not exist. This behavior was introduced in this PR apache#5319  as part of updating the tool to use latest consumer API. However, if we run the tool with producer acks == 1, the high watermark may not be updated before we reset consumer offsets to latest. In rare cases when this happens, the tool will throw an exception in the for loop where the consumer will unexpectedly consume the dummy record. As a result, we occasionally see Benchmark.test_end_to_end_latency system test failures.

This PR checks if topic exists, and creates the topic using AdminClient if it does not exist.

Author: Anna Povzner <anna@confluent.io>

Reviewers: Ismael Juma <ismael@juma.me.uk>, Ewen Cheslack-Postava <ewen@confluent.io>

Closes apache#5950 from apovzner/fix-EndToEndLatency
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants